
<template>
  <div class="container">
    <div ref="chart" class="echart"/>
    <p class="overlay">{{ stockName }} {{ stockCode }} {{  stockTime  }}</p>
  </div>
</template>  
<script>
import * as echarts from 'echarts';
import axios from 'axios';

export default {
  data() {
    return {
      code:'600733',
      dayTime:'2024-11-15',
      dayCount:0,
      upColor: '#FD1050',
      downColor: '#0CF49B',
      M0Color:'#FD1050',
      M5Color:'#000',
      M10Color:'yellow',
      M20Color:'#800080',
      M30Color:'green',
      M60Color:'blue',

      startPercent:80,
      endPercent:100,

      volume:[],
      close:[],
      volData:[],
      closePrice:[],
      highPrice:[],
      lowPrice:[],
      recordDate:[],
      kLineData:[ // open, close, high, low
        [150, 250, 350, 400],
        [370, 270, 570, 500],
        // ... 更多K线数据
      ],
      yAxisMin: 0,
      yAxisMax: 10,
    }
  },
  props: {
        num: 0,
  },
  watch: {
      num(val,oldValue) {
        this.dayCount = val
        this.fetchData();
      }
      // stockCode(newValue, oldValue) {
      //   console.log('stockCode', newValue, oldValue);
      // }
  },
  computed: {
    stockCode() {  
      const value = this.$store.getters.getStockCode
      console.log('stockCode', value);
      this.code = value;
      this.fetchData();
      return value;
    },
    stockName() {
      const value = this.$store.getters.getStockName;
      return value;
    },
    stockTime() {
      const value = this.$store.getters.getStockTime;
      this.dayTime = value;
      this.fetchData();
      return value;
    }
  },
  mounted() {
    // this.initChart();
    this.fetchData();
  },
  methods: {
    initChart() {
      // 基于准备好的dom，初始化echarts实例
      const myChart = echarts.init(this.$refs.chart);
      // 指定图表的配置项和数据
      const option = {
        xAxis: [
          {
            data: this.recordDate,
            axisLabel: {// x轴标签相关设置
              formatter: function (value, index) {
                  return value.slice(0,  10);
              }
            }
          },
          {
            data: this.recordDate,
            axisLabel: {// x轴标签相关设置
              formatter: function (value, index) {
                  return value.slice(0,  10);
              }
            },
            gridIndex: 1,
          },
        ],

        yAxis: [{  
            type: 'value',  
            min: this.yAxisMin,
            max: this.yAxisMax,
            // 其他配置...  
            axisLine: {  
                // 这里设置Y轴主线的样式，但它通常不是我们要关注的  
                lineStyle: {  
                    color: '#000'  
                }  
            },  
            splitLine: {  
                // 将Y轴的分割线设置为虚线  
                show: true,  
                lineStyle: {  
                    type: 'dashed', // 设置为虚线  
                    color: '#ccc' // 分割线颜色  
                }  
            }  
        },{
          name: '成交量',  
          gridIndex: 1,
          axisLabel: {// x轴标签相关设置
            formatter: function (value, index) {
                return index == 0 ? "(万)" : value;
            }
          }
        }],  

        grid: [
          {
            top:"1%",
            bottom: "40%",
          },
          {
            top: "73%",
          },
        ],  

        series: [{
          name: 'kLine',
          data: this.kLineData,
          type: 'candlestick',// 显示种类,如线性等       
          itemStyle: {// 对象样式
              normal: {
                  color: this.upColor,
                  color0: this.downColor,
                  borderColor: this.upColor,
                  borderColor0: this.downColor
              }
          }
        },{
            name:"volunm",
            type: "bar",
            data: this.volume,
            xAxisIndex: 1,
            yAxisIndex: 1,
            itemStyle: {   
              color: (params) => {
                return this.close[params.dataIndex] > 0 ? this.upColor : this.downColor; 
              }
            }  
          },
 
          {
            name: 'MA5',
            type: 'line',
            data: this.calculateMA(5,this.closePrice),
            smooth: true,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M5Color,
                width: 1
              }
            },
          },
          {
            name: 'MA10',
            type: 'line',
            data: this.calculateMA(10,this.closePrice),
            smooth: true,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M10Color,
                width: 1
              }
            },
          },
          {
            name: 'MA20',
            type: 'line',
            data: this.calculateMA(20,this.closePrice),
            smooth: true,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M20Color,
                width: 1
              }
            },
          },
          {
            name: 'MA30',
            type: 'line',
            data: this.calculateMA(30,this.closePrice),
            smooth: true,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M30Color,
                width: 1
              }
            },
          },
          {
            name: 'MA60',
            type: 'line',
            data: this.calculateMA(60,this.closePrice),
            smooth: true,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M60Color,
                width: 1
              }
            },
          },
          {
            name: '量能指标',
            type: 'line',
            data: this.volData,
            smooth: false,
            symbol: "none", //隐藏选中时有小圆点
            lineStyle: {
              normal: {
                opacity: 0.8,
                color: this.M60Color,
                width: 3
              }
            },
          },],

        dataZoom: [  
          {  
              type: 'slider', // 设置为slider类型  
              show: true, // 是否显示滑动条  
              xAxisIndex: [0,1], // 指定作用于哪个坐标轴，K线图通常只有一个x轴  
              start: this.startPercent, // 初始时数据窗口的起始百分比  
              end: this.endPercent, // 初始时数据窗口的结束百分比，这里只显示10%的数据  
              // 其他可选配置...  
          },  
          {  
              type: 'inside', // 另一种dataZoom，允许通过鼠标滚轮缩放  
              xAxisIndex: [0,1],  
              zoomOnMouseWheel: true, // 是否启用鼠标滚轮缩放  
          }  
        ],

        tooltip: {  
            trigger: 'axis', // 触发类型，默认数据项触发，可选为：'item' | 'axis'  
            formatter: (params, ticket, callback) => {
              const item = params[0];
              var html = ""
              if (item.seriesName === "kLine") {
                // console.log('params:', params[0]);
                var volume =this.volume[item.dataIndex];
                var change = this.close[item.dataIndex];
                var upDown = change > 0 ? '+' : '';
                var color = change > 0 ? 'style="color:#ff4242"' : 'style="color:#26bf66"';
                var normalColor = "color:#333"
                
                html = '<div class="commColor" style="width:100px;margin-right: 25px;">';
                html += '<div>日期  <span  '+normalColor+' >' + this.recordDate[item.dataIndex].slice(0, 10) + '</span></div>';
                html += '<div>开盘  <span  '+normalColor+' >' + item.data[1] + '</span></div>';
                html += '<div>收盘  <span  '+color+' >' + item.data[2] + '</span></div>';
                html += '<div>最高  <span  '+normalColor+' >' + item.data[3]+ '</span></div>';
                html += '<div>最低  <span  '+normalColor+' >' + item.data[4] + '</span></div></div>';
                html += '<div>涨跌  <span  '+color+' ><strong>' + upDown + change.toFixed(2) + '%</strong></span></div></div>';
                html += '<div>成交量  <span  '+normalColor+' >' + volume + '亿</span></div></div>';
                return html;
            //           var color ='style="color:#ff4242"';
              } else {
                var volume =this.volume[item.dataIndex];
                var change = this.close[item.dataIndex];
                var color = change > 0 ? 'style="color:#ff4242"' : 'style="color:#26bf66"';
                html = '<div class="commColor" style="width:100px;margin-right: 20px;">';
                html += '<div>日期  <span  '+normalColor+' >' + this.recordDate[item.dataIndex].slice(0, 10) + '</span></div>';             
                html += '<div>成交量  <span  '+color+' >' + volume + '万</span></div></div>';
                return html;
              }
              return html;
            },
            axisPointer: {  
                type: 'cross', // 默认为直线，可选为：'line' | 'shadow'  
            }  
        }, 
      };
      // 使用刚指定的配置项和数据显示图表。
      myChart.setOption(option);

      var isChange = false;
      // 定义一个定时任务来定期更新数据
      let intervalId = setInterval(() => {
          if (isChange) {
            isChange = false;
            this.calculateHighLow();
            console.log('Updating data every 1 second...' + this.startPercent + '  ' + this.endPercent);
          }    
      }, 2000); // 每隔 1 秒执行一次
      myChart.on('datazoom', (params) => { 
        isChange = true; 
        if (params.start == null) {
          this.startPercent = params.batch[0].start;
          this.endPercent = params.batch[0].end;
          console.log('位置更新1...' + this.startPercent + '  ' + this.endPercent);
        } else {
          this.startPercent = params.start
          this.endPercent = params.end
          console.log('位置更新2...' + this.startPercent + '  ' + this.endPercent);
        }
      });
    },

    async fetchData() {  
      try { 
        var api = "api/plat/stock/getStockTimeData?stockCode=" + this.code + "&dayCount=" + this.dayCount + "&allCount=200" +  "&dayTime=" + this.dayTime;
        const response = await axios.get(api);  
        const result = response.data;
        console.log('请求结果:', result);
        if (result.status == 200) {  
          console.log('请求成功:', result);
          this.kLineData = []; 
          this.volume = [];
          this.close = [];
          this.recordDate = [];
          this.volData = [];
          this.closePrice = [];
          this.highPrice = [];
          this.lowPrice = [];
          result.data = result.data.reverse()
          result.data.forEach(item => {   
            // 对item进行所需的操作 
            this.volData.push(item.volData) 
            this.closePrice.push(item.closePrice) 
            this.highPrice.push(item.maxPrice) 
            this.lowPrice.push(item.minPrice) 
            const arr = [item.openPrice, item.closePrice, item.maxPrice, item.minPrice]
            this.kLineData.push(arr) 
            this.recordDate.push(item.recordDate)
            this.volume.push(Number(item.volume / 10000).toFixed(2))
            this.close.push(item.close)
          }); 

          this.calculateHighLow();
          
           
        } else {
          console.error('请求失败:');
        }     
      } catch (error) {  
        console.error('请求error:', error);  
      }  
    },

    calculateHighLow() {

      // 计算最大值和最小值
      var startIndex = Math.round(this.highPrice.length * (this.startPercent / 100));
      var endIndex = Math.round(this.highPrice.length * (this.endPercent / 100)); 
      var highs = this.highPrice.slice(startIndex,endIndex);
      var lows = this.lowPrice.slice(startIndex,endIndex);
      const maxPrice = Math.max(...highs); // 找到最高价中的最大值
      const minPrice = Math.min(...lows); // 找到最低价中的最小
      // 自定义 y 轴的范围
      this.yAxisMin = (minPrice - (maxPrice - minPrice) * 0.1).toFixed(2)
      this.yAxisMax = (maxPrice + (maxPrice - minPrice) * 0.1).toFixed(2)

      this.initChart();
      // console.log("开始：" + startIndex,"结束：" + endIndex); 

    },
    //================================MA计算公式
    calculateMA(dayCount,data) {
      var result = [];
      for (var i = 0; i < data.length; i++) {
        if (i < dayCount) {
          result.push('-');
          continue;
        }
        var sum = 0;
        for (var j = 0; j < dayCount; j++) {
          sum += data[i - j];
        }
        result.push((sum / dayCount).toFixed(2));
      }
      console.log(result)
      return result;
    },
  
  },
}
</script>
  
<style scoped>
.echart {
  float: left;
  width: 1000px; height: 500px;
}
.container {
    flex: 100; /* 75% */
}
.overlay {
  position: absolute; /* 设置为绝对定位 */
  top: 12%;
  left: 60%;
  display: flex;
  justify-content: center;
  align-items: center;
  font-size: 17px;
  font-weight: bold;
  font-family: 'Hiragino Sans GB'/* Inter, 'Helvetica Neue', Helvetica, 'PingFang SC',
  'Hiragino Sans GB', 'Microsoft YaHei' */
}
</style>
  